﻿using Microsoft.Extensions.DependencyInjection;
using Singer.BackgroundJob.RabbitMQ.Contracts;
using Singer.Shared.Contracts.Tenant;
using Singer.Shared.Contracts.Tenant.Dtos;
using Singer.Shared.Contracts.User;
using Singer.Shared.Contracts.User.Dtos;
using Singer.Shared.UserContext;

namespace Singer.BackgroundJob.RabbitMQ;

/// <summary>
/// 后台任务，服务提供 工厂
/// </summary>
internal class BackgroundJobServiceFactory
{
    /// <summary>
    /// 程序运行时创建的DI，仅包含单例服务
    /// </summary>
    IServiceProvider AppRootService;

    /// <summary>
    /// 后台任务，服务提供 工厂 构造函数
    /// </summary>
    /// <param name="appRootService">程序运行时创建的DI，仅包含单例服务</param>
    internal BackgroundJobServiceFactory(IServiceProvider appRootService)
    {
        AppRootService = appRootService;
    }

    /// <summary>
    /// 作用域服务创建，处理
    /// </summary>
    /// <param name="args">后台任务 参数</param>
    internal async Task<IServiceScope> CreateServiceScope(BackgroundJobMessage message)
    {
        IServiceScope serviceScope = AppRootService.CreateScope(); // 服务作用域
        try
        {
            IServiceProvider serviceProvider = serviceScope.ServiceProvider;

            // 用户信息上下文处理
            IUserContextAccessor userContextAccessor = serviceProvider.GetRequiredService<IUserContextAccessor>();
            DefaultUserContext userContext = new DefaultUserContext();

            // 用户信息
            if (!string.IsNullOrWhiteSpace(message.CurrentUserId))
            {
                IUserInfoProvider? userInfoProvider = serviceProvider.GetService<IUserInfoProvider>();
                if (userInfoProvider != null)
                {
                    SysUserInfo? userInfo = await userInfoProvider.GetSysUserInfoAsync(message.CurrentUserId);
                    if (userInfo != null)
                    {
                        userContext.UserId = userInfo.UserId;
                        userContext.UserName = userInfo.UserName;
                        userContext.Mobile = userInfo.Mobile;
                    }
                }
            }

            // 租户信息
            if (!string.IsNullOrWhiteSpace(message.CurrentTenantId))
            {
                ITenantInfoProvider? tenantInfoProvider = serviceProvider.GetService<ITenantInfoProvider>();
                if (tenantInfoProvider != null)
                {
                    SysTenantInfo? tenantInfo = await tenantInfoProvider.GetSysTenantInfoAsync(message.CurrentTenantId);
                    if (tenantInfo != null)
                    {
                        userContext.TenantId = tenantInfo.TenantId;
                        userContext.TenantCode = tenantInfo.TenantCode;
                        userContext.TenantName = tenantInfo.TenantName;
                    }
                }
            }
            userContextAccessor.UserContext = userContext;

            // 其他需要特殊处理的作用域服务 处理逻辑 ...

            return serviceScope;
        }
        catch (Exception)
        {
            serviceScope.Dispose();
            throw;
        }
    }
}
